package main

import "fmt"

func main() {
	r, _ := f("1+1* (2+3-(2/2+1))", 0)
	fmt.Println(r)
}

// 从s[start]开始出发，返回自己负责的这一段计算的结果，
// 需要返回结果和结束的位置，为了上游函数知道接下来从哪里开始接着计算
func f(s string, start int) (result, where int) {
	tmpResult := 0
	stackNumer := []int{}
	stackY := []byte{}
	for start < len(s) && s[start] != ')' {
		if s[start] == ' ' {
			start++
			continue
		}
		// 如果碰到的是数字
		if isNumber(s[start]) {
			tmpResult = tmpResult*10 + int((rune(s[start]) - rune('0')))
			start++
		} else if !isLeftKuoHao(s[start]) {
			// 如果碰到的是+ - * /
			stackNumer, stackY = push(stackNumer, stackY, tmpResult, s[start])
			tmpResult = 0
			start++
		} else {
			// 如果碰到的是左括号
			tmpResult, where = f(s, start+1)
			start = where + 1
		}
	}
	stackNumer, stackY = push(stackNumer, stackY, tmpResult, '+')
	where = start
	return compute(stackNumer, stackY), where
}

func compute(stackNumer []int, stackY []byte) int {
	cur := stackNumer[0]
	for i := 0; i < len(stackNumer)-1; i++ {
		s := stackY[i]
		if s == '+' {
			cur += stackNumer[i+1]
		} else {
			cur -= stackNumer[i+1]
		}
	}
	return cur
}

func push(stackNumer []int, stackY []byte, tmpResult int, s byte) ([]int, []byte) {
	l := len(stackY)
	if l > 0 && (stackY[l-1] == '*' || stackY[l-1] == '/') {
		num := stackNumer[len(stackNumer)-1]
		if stackY[l-1] == '*' {
			num *= tmpResult
		} else {
			num /= tmpResult
		}
		stackNumer[len(stackNumer)-1] = num
		stackY[l-1] = s
	} else {
		stackNumer = append(stackNumer, tmpResult)
		stackY = append(stackY, s)
	}
	return stackNumer, stackY
}

func isNumber(s byte) bool {
	return rune(s) >= rune('0') && rune(s) <= rune('9')
}

func isLeftKuoHao(s byte) bool {
	return rune(s) == rune('(')
}
